#ifndef FALCON_PREPROCESSOR_COMPARISON_HPP
#define FALCON_PREPROCESSOR_COMPARISON_HPP

//@{
#define __FALCON_MEMBER_COMPARISON_OPERATOR(_Type, _Operator, _Code)\
	inline bool operator _Operator(const _Type& other) const\
	{ return (_Code); }

#define __FALCON_MEMBER_COMPARISON2_OPERATOR(_Operator, _Type, _Value1, _Value2)\
	__FALCON_MEMBER_COMPARISON_OPERATOR(_Type, _Operator, (_Value1) == (_Value2))

#define FALCON_MEMBER_COMPARISON_OPERATOR(_Type, _Value, _Operator)\
	__FALCON_MEMBER_COMPARISON_OPERATOR(_Type, _Operator, _Value _Operator other)

#define FALCON_MEMBER_EQUAL_OPERATOR(_Type, _Value)\
	FALCON_MEMBER_COMPARISON_OPERATOR(_Type, _Value, ==)\
	__FALCON_MEMBER_COMPARISON_OPERATOR(_Type, !=, !operator==(other))

#define FALCON_MEMBER_EQUAL2_OPERATOR(_Type, _Value1, _Value2)\
	__FALCON_MEMBER_COMPARISON2_OPERATOR(==, _Type, _Value1, _Value2)\
	__FALCON_MEMBER_COMPARISON_OPERATOR(_Type, !=, !operator==(other))

#define FALCON_MEMBER_COMPARISON_MINIMAL_OPERATOR(_Type, _Value)\
	FALCON_MEMBER_COMPARISON_OPERATOR(_Type, _Value, ==)\
	FALCON_MEMBER_COMPARISON_OPERATOR(_Type, _Value, <)

#define FALCON_MEMBER_COMPARISON2_MINIMAL_OPERATOR(_Type, _Value1, _Value2)\
	__FALCON_MEMBER_COMPARISON2_OPERATOR(==, _Type, _Value1, _Value2)\
	__FALCON_MEMBER_COMPARISON2_OPERATOR(<, _Type, _Value1, _Value2)

#define FALCON_MEMBER_COMPARISON_OTHER_OPERATOR(_Type)\
	__FALCON_MEMBER_COMPARISON_OPERATOR(_Type, !=, !operator==(other))\
	__FALCON_MEMBER_COMPARISON_OPERATOR(_Type, <=, operator<(other) && operator==(other))\
	__FALCON_MEMBER_COMPARISON_OPERATOR(_Type, >, !operator<=(other))\
	__FALCON_MEMBER_COMPARISON_OPERATOR(_Type, >=, !operator<(other))

#define FALCON_MEMBER_COMPARISON_ALL_OPERATOR(_Type, _Value)\
	FALCON_MEMBER_COMPARISON_MINIMAL_OPERATOR(_Type, _Value)\
	FALCON_MEMBER_COMPARISON_OTHER_OPERATOR(_Type)

#define FALCON_MEMBER_COMPARISON2_ALL_OPERATOR(_Type, _Value1, _Value2)\
	FALCON_MEMBER_COMPARISON2_MINIMAL_OPERATOR(_Type, _Value1, _Value2)\
	FALCON_MEMBER_COMPARISON_OTHER_OPERATOR(_Type)
//@}

//@{
#define __FALCON_FUNCTION_COMPARISON2_OPERATOR(_Type, _Type2, _Operator, _Code)\
	inline bool operator _Operator(const _Type& v1, const _Type& v2) const\
	{ return (_Code); }

#define FALCON_FUNCTION_COMPARISON2_OPERATOR(_Type, _Type2, _Value, _Value2, _Operator)\
	__FALCON_FUNCTION_COMPARISON2_OPERATOR(_Type, _Type2, _Operator, _Value _Operator _Value2)

#define FALCON_FUNCTION_COMPARISON2_MINIMAL_OPERATOR(_Type, _Type2, _Value, _Value2)\
	FALCON_FUNCTION_COMPARISON2_OPERATOR(_Type, _Type2, _Value, _Value2, ==)\
	FALCON_FUNCTION_COMPARISON2_OPERATOR(_Type, _Type2, _Value, _Value2, <)

#define FALCON_FUNCTION_COMPARISON2_OTHER_OPERATOR(_Type, _Type2)\
	__FALCON_FUNCTION_COMPARISON2_OPERATOR(_Type, _Type2, !=, !(v1==v2))\
	__FALCON_FUNCTION_COMPARISON2_OPERATOR(_Type, _Type2, <=, v1<v2 && v1==v2)\
	__FALCON_FUNCTION_COMPARISON2_OPERATOR(_Type, _Type2, >, !(v1<=v2))\
	__FALCON_FUNCTION_COMPARISON2_OPERATOR(_Type, _Type2, >=, !(v1<v2))

#define FALCON_FUNCTION_COMPARISON2_ALL_OPERATOR(_Type, _Type2, _Value, _Value2)\
	FALCON_FUNCTION_COMPARISON2_MINIMAL_OPERATOR(_Type, _Type2, _Value, _Value2)\
	FALCON_FUNCTION_COMPARISON2_OTHER_OPERATOR(_Type, _Type2)
//@}


//@{
#define FALCON_FUNCTION_COMPARISON2_OPERATOR_LEFT(_Type, _Type2, _Operator)\
	__FALCON_FUNCTION_COMPARISON2_OPERATOR(_Type, _Type2, _Operator, v2 _Operator v1)

#define FALCON_FUNCTION_COMPARISON2_MINIMAL_OPERATOR_LEFT(_Type, _Type2)\
	FALCON_FUNCTION_COMPARISON2_OPERATOR_LEFT(_Type, _Type2, ==)\
	FALCON_FUNCTION_COMPARISON2_OPERATOR_LEFT(_Type, _Type2, <)\

#define FALCON_FUNCTION_COMPARISON2_OTHER_OPERATOR_LEFT(_Type, _Type2)\
	FALCON_FUNCTION_COMPARISON2_OPERATOR_LEFT(_Type, _Type2, !=)\
	FALCON_FUNCTION_COMPARISON2_OPERATOR_LEFT(_Type, _Type2, <=)\
	FALCON_FUNCTION_COMPARISON2_OPERATOR_LEFT(_Type, _Type2, >)\
	FALCON_FUNCTION_COMPARISON2_OPERATOR_LEFT(_Type, _Type2, >=)

#define FALCON_FUNCTION_COMPARISON2_ALL_OPERATOR_LEFT(_Type, _Type2)\
	FALCON_FUNCTION_COMPARISON2_MINIMAL_OPERATOR_LEFT(_Type, _Type2)\
	FALCON_FUNCTION_COMPARISON2_OTHER_OPERATOR_LEFT(_Type, _Type2)
//@}


//@{
#define FALCON_FUNCTION_COMPARISON_OPERATOR(_Type, _PostCode, _Operator)\
	FALCON_FUNCTION_COMPARISON2_OPERATOR(_Type, _Type, v1 _PostCode, v2 _PostCode, _Operator)

#define FALCON_FUNCTION_COMPARISON_MINIMAL_OPERATOR(_Type, _PostCode)\
	FALCON_FUNCTION_COMPARISON_OPERATOR(_Type, _PostCode, ==)\
	FALCON_FUNCTION_COMPARISON_OPERATOR(_Type, _PostCode, <)\

#define FALCON_FUNCTION_COMPARISON_OTHER_OPERATOR(_Type, _PostCode)\
	FALCON_FUNCTION_COMPARISON_OPERATOR(_Type, _PostCode, !=)\
	FALCON_FUNCTION_COMPARISON_OPERATOR(_Type, _PostCode, <=)\
	FALCON_FUNCTION_COMPARISON_OPERATOR(_Type, _PostCode, >)\
	FALCON_FUNCTION_COMPARISON_OPERATOR(_Type, _PostCode, >=)

#define FALCON_FUNCTION_COMPARISON_ALL_OPERATOR(_Type, _PostCode)\
	FALCON_FUNCTION_COMPARISON_MINIMAL_OPERATOR(_Type, _PostCode)\
	FALCON_FUNCTION_COMPARISON_OTHER_OPERATOR(_Type, _PostCode)
//@}

#endif